package com.jillchen.grpc.server.convertprovidors;


import com.aspose.pdf.*;
import com.aspose.pdf.devices.EmfDevice;
import com.aspose.pdf.devices.Resolution;
import com.aspose.pdf.devices.TextDevice;
import com.jillchen.grpc.server.utils.AbsConverter;
import org.apache.commons.io.FilenameUtils;

import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.nio.charset.Charset;
import java.util.Arrays;

public class ConvertPdf extends AbsConverter {
    @Override
    public int Convert(String InFile, String OutFile) {
        try {

            long old = System.currentTimeMillis();
            String FileExt = FilenameUtils.getExtension(OutFile).toUpperCase();
            if ("TXT".equals(FileExt)) {

                // open document
                Document pdfDocument = new Document(InFile);
                // text file in which extracted text will be saved
                java.io.OutputStream text_stream = new java.io.FileOutputStream(OutFile, true);
                // iterate through all the pages of PDF file
                for (Page page : (Iterable<Page>) pdfDocument.getPages()) {
                    // create text device
                    TextDevice textDevice = new TextDevice();
                    // set text extraction options - set text extraction mode (Raw or
                    // Pure)

                    Charset charset = Charset.forName("GBK");
                    textDevice.setEncoding(charset);
                    TextExtractionOptions textExtOptions = new TextExtractionOptions(TextExtractionOptions.TextFormattingMode.Raw);
                    textDevice.setExtractionOptions(textExtOptions);
                    // get the text from pages of PDF and save it to OutputStream object
                    textDevice.process(page, text_stream);
                }
                // close stream object
                text_stream.close();
            } else if ("XLS".equals(FileExt) || "XLSX".equals(FileExt)) {
                // Load PDF document
                Document pdfDocument = new Document(InFile);
                // Instantiate ExcelSave Option object
                ExcelSaveOptions excelsave = new ExcelSaveOptions();
                // Save the output to XLS format
                pdfDocument.save(OutFile, excelsave);
            } else if ("DOC".equals(FileExt)) {
                // Open the source PDF document
                Document pdfDocument = new Document(InFile);
                // Save the file into Microsoft document format
                pdfDocument.save(OutFile, SaveFormat.Doc);

            } else if ("DOCX".equals(FileExt)) {
                Document pdfDocument = new Document(InFile);
                // Instantiate Doc SaveOptions instance
                DocSaveOptions saveOptions = new DocSaveOptions();
                // Set output file format as DOCX
                saveOptions.setFormat(DocSaveOptions.DocFormat.DocX);
                // Save resultant DOCX file
                pdfDocument.save(OutFile, saveOptions);
            } else if ("HTML".equals(FileExt)) {
                Document doc = new Document(InFile);
                // Instantiate HTML Save options object
                HtmlSaveOptions newOptions = new HtmlSaveOptions();

                // Enable option to embed all resources inside the HTML
                newOptions.PartsEmbeddingMode = HtmlSaveOptions.PartsEmbeddingModes.EmbedAllIntoHtml;
                // This is just optimization for IE and can be omitted
                newOptions.LettersPositioningMethod = LettersPositioningMethods.UseEmUnitsAndCompensationOfRoundingErrorsInCss;
                newOptions.RasterImagesSavingMode = HtmlSaveOptions.RasterImagesSavingModes.AsEmbeddedPartsOfPngPageBackground;
                newOptions.FontSavingMode = HtmlSaveOptions.FontSavingModes.SaveInAllFormats;
                // Output file path

                // Save the output file
                doc.save(OutFile, newOptions);
            } else if ("EPUB".equals(FileExt)) {
                // Load PDF document
                Document pdfDocument = new Document(InFile);
                // Instantiate EPUB Save options
                EpubSaveOptions options = new EpubSaveOptions();
                // Specify the layout for contents
                options.ContentRecognitionMode = EpubSaveOptions.RecognitionMode.Flow;
                // Save the EPUB document
                pdfDocument.save(OutFile, options);
            }else if("SVG".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(InFile);
                // instantiate an object of SvgSaveOptions
                SvgSaveOptions saveOptions = new SvgSaveOptions();
                // do not compress SVG image to Zip archive
                saveOptions.CompressOutputToZipArchive = false;
                doc.save(OutFile, saveOptions);

            }else if("PPTX".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(InFile);
                PptxSaveOptions pptx_save = new PptxSaveOptions();
                doc.save(OutFile, pptx_save);
            }

            else if("EMF".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(InFile);
                // instantiate EmfDevice object

                java.io.OutputStream text_stream = new java.io.FileOutputStream(OutFile, true);
                for (Page page : (Iterable<Page>) doc.getPages()) {
                    EmfDevice device = new EmfDevice(new Resolution(96));
                    device.process(page, text_stream);
                }
                text_stream.close();
            }

            long now = System.currentTimeMillis();
            System.out.println("convert OK! " + ((now - old) / 1000.0) + "s");
            return 0;
        } catch (Exception ex) {
            System.out.println(ex.getMessage() + "\r\n" + Arrays.toString(ex.getStackTrace()));
            return -3;
        }
    }

    @Override
    public int Convert(InputStream inputStream, String InFile, ByteArrayOutputStream outputStream, String OutFile) {
        try {

            long old = System.currentTimeMillis();
            String FileExt = FilenameUtils.getExtension(OutFile).toUpperCase();
            if ("TXT".equals(FileExt)) {
                Document pdfDocument = new Document(inputStream);
                java.io.OutputStream text_stream = new java.io.FileOutputStream(OutFile, true);
                for (Page page : (Iterable<Page>) pdfDocument.getPages()) {
                    TextDevice textDevice = new TextDevice();
                    Charset charset = Charset.forName("GBK");
                    textDevice.setEncoding(charset);
                    TextExtractionOptions textExtOptions = new TextExtractionOptions(TextExtractionOptions.TextFormattingMode.Raw);
                    textDevice.setExtractionOptions(textExtOptions);
                    textDevice.process(page, text_stream);
                }
                outputStream= (ByteArrayOutputStream)text_stream;
                text_stream.close();
            } else if ("XLS".equals(FileExt) || "XLSX".equals(FileExt)) {
                // Load PDF document
                Document pdfDocument = new Document(inputStream);
                // Instantiate ExcelSave Option object
                ExcelSaveOptions excelsave = new ExcelSaveOptions();
                // Save the output to XLS format
                pdfDocument.save(outputStream, excelsave);
            } else if ("DOC".equals(FileExt)) {
                // Open the source PDF document
                Document pdfDocument = new Document(inputStream);
                // Save the file into Microsoft document format
                pdfDocument.save(outputStream, SaveFormat.Doc);

            } else if ("DOCX".equals(FileExt)) {
                Document pdfDocument = new Document(inputStream);
                // Instantiate Doc SaveOptions instance
                DocSaveOptions saveOptions = new DocSaveOptions();
                // Set output file format as DOCX
                saveOptions.setFormat(DocSaveOptions.DocFormat.DocX);
                // Save resultant DOCX file
                pdfDocument.save(outputStream, saveOptions);
            } else if ("HTML".equals(FileExt)) {
                Document doc = new Document(inputStream);
                // Instantiate HTML Save options object
                HtmlSaveOptions newOptions = new HtmlSaveOptions();

                // Enable option to embed all resources inside the HTML
                newOptions.PartsEmbeddingMode = HtmlSaveOptions.PartsEmbeddingModes.EmbedAllIntoHtml;
                // This is just optimization for IE and can be omitted
                newOptions.LettersPositioningMethod = LettersPositioningMethods.UseEmUnitsAndCompensationOfRoundingErrorsInCss;
                newOptions.RasterImagesSavingMode = HtmlSaveOptions.RasterImagesSavingModes.AsEmbeddedPartsOfPngPageBackground;
                newOptions.FontSavingMode = HtmlSaveOptions.FontSavingModes.SaveInAllFormats;
                // Output file path

                // Save the output file
                doc.save(outputStream, newOptions);
            } else if ("EPUB".equals(FileExt)) {
                // Load PDF document
                Document pdfDocument = new Document(inputStream);
                // Instantiate EPUB Save options
                EpubSaveOptions options = new EpubSaveOptions();
                // Specify the layout for contents
                options.ContentRecognitionMode = EpubSaveOptions.RecognitionMode.Flow;
                // Save the EPUB document
                pdfDocument.save(outputStream, options);
            }else if("SVG".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(inputStream);
                // instantiate an object of SvgSaveOptions
                SvgSaveOptions saveOptions = new SvgSaveOptions();
                // do not compress SVG image to Zip archive
                saveOptions.CompressOutputToZipArchive = false;
                doc.save(outputStream, saveOptions);

            }else if("PPTX".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(inputStream);
                PptxSaveOptions pptx_save = new PptxSaveOptions();
                doc.save(outputStream, pptx_save);
            }else if("EMF".equals(FileExt))
            {
                // load PDF document
                Document doc = new Document(inputStream);
                // instantiate EmfDevice object

                java.io.OutputStream text_stream = new java.io.FileOutputStream(OutFile, true);
                for (Page page : (Iterable<Page>) doc.getPages()) {
                    EmfDevice device = new EmfDevice(new Resolution(96));
                    device.process(page, text_stream);
                }
                outputStream= (ByteArrayOutputStream)text_stream;
                text_stream.close();
            }

            long now = System.currentTimeMillis();
            System.out.println("convert OK! " + ((now - old) / 1000.0) + "s");
            return 0;

        } catch (Exception ex) {
            System.out.println(ex.getMessage() + "\r\n" + Arrays.toString(ex.getStackTrace()));
            return -3;
        }
    }

}
